package com.fenger.billbar.demo;

import java.awt.Color;
import java.awt.GraphicsConfiguration;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;
import javax.media.j3d.AmbientLight;
import javax.media.j3d.Appearance;
import javax.media.j3d.Background;
import javax.media.j3d.BoundingSphere;
import javax.media.j3d.BranchGroup;
import javax.media.j3d.Canvas3D;
import javax.media.j3d.DirectionalLight;
import javax.media.j3d.Material;
import javax.media.j3d.TextureAttributes;
import javax.media.j3d.Transform3D;
import javax.media.j3d.TransformGroup;
import javax.vecmath.Color3f;
import javax.vecmath.Point3d;
import javax.vecmath.Vector3d;

import com.sun.j3d.utils.behaviors.mouse.MouseRotate;
import com.sun.j3d.utils.behaviors.mouse.MouseTranslate;
import com.sun.j3d.utils.behaviors.mouse.MouseWheelZoom;
import com.sun.j3d.utils.geometry.Sphere;
import com.sun.j3d.utils.image.TextureLoader;
import com.sun.j3d.utils.universe.SimpleUniverse;

public class Ball extends javax.swing.JFrame {
	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	private javax.swing.JPanel drawingPanel;

	public Ball() throws IOException {
		// Initialize the GUI components
		initComponents();
		GraphicsConfiguration configuration = SimpleUniverse.getPreferredConfiguration();
		// 构造新的Canvas3D
		Canvas3D canvas3D = new Canvas3D(configuration);
		// 创建虚拟空间
		SimpleUniverse universe = new SimpleUniverse(canvas3D);
		// 将内容子图插入虚拟空间的Locale中
		universe.addBranchGraph(getBranchGroup());
		// 安放观察点
		universe.getViewingPlatform().setNominalViewingTransform();

		/*
		 * OrbitBehavior 类允许您使用鼠标方便地移动视图。当用户移动鼠标时，它会平移、旋转以及缩放场景。下面的代码片段将
		 * OrbitBehavior 添加到 ViewingPlatform 中。无需其它代码。（我们稍后将讨论界限球和行为。）
		 */
		/*
		 * OrbitBehavior orbit = new OrbitBehavior(canvas3D); BoundingSphere
		 * bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 0.5);
		 * orbit.setSchedulingBounds(bounds);
		 * universe.getViewingPlatform().setViewPlatformBehavior(orbit);
		 */

		drawingPanel.add(canvas3D, java.awt.BorderLayout.CENTER);
	}

	private void initComponents() {
		drawingPanel = new javax.swing.JPanel();

		setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);
		setTitle("桌球");
		drawingPanel.setLayout(new java.awt.BorderLayout());
		drawingPanel.setPreferredSize(new java.awt.Dimension(600, 800));
		getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER);

		pack();
	}

	/**
	 * 构建内容子图
	 * 
	 * @return
	 * @throws IOException
	 */
	BranchGroup getBranchGroup() throws IOException {
		BranchGroup branchGroup = new BranchGroup();
		BoundingSphere bounds = new BoundingSphere(new Point3d(0, 2.0, 7.0), 1000.0);
		// set coordinates
		Transform3D transform3D = new Transform3D();
		transform3D.setTranslation(new Vector3d(0, 0, -.8));
		// Matrix3d martix = new Matrix3d(0, 0, 0, 1, 1, 1, 0, 0,0);
		// transform3D.setRotation(martix );
		// transform3D.setRotation(new Quat4d(2d, 0d, 0d, 0d));
		TransformGroup transformGroup = new TransformGroup();
		// transformGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_READ);
		transformGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
		transformGroup.setTransform(transform3D);

		// 设置背景
		Color3f backgroudColor3f = new Color3f(Color.GRAY);
		Background background = new Background(backgroudColor3f);
		background.setApplicationBounds(bounds);
		branchGroup.addChild(background);
		// 设置鼠标事件
		MouseRotate mouseRotate = new MouseRotate();
		mouseRotate.setTransformGroup(transformGroup);
		mouseRotate.setSchedulingBounds(bounds);
		transformGroup.addChild(mouseRotate);

		MouseWheelZoom mouseZoom = new MouseWheelZoom();
		mouseZoom.setTransformGroup(transformGroup);
		mouseZoom.setSchedulingBounds(bounds);
		transformGroup.addChild(mouseZoom);

		MouseTranslate mouseTranslate = new MouseTranslate();
		mouseTranslate.setTransformGroup(transformGroup);
		mouseTranslate.setSchedulingBounds(bounds);
		transformGroup.addChild(mouseTranslate);

		// throw in some light so we aren't stumbling
		// around in the dark
		Color3f lightColor = new Color3f(Color.yellow);
		AmbientLight ambientLight = new AmbientLight(lightColor);
		ambientLight.setInfluencingBounds(bounds);
		branchGroup.addChild(ambientLight);
		DirectionalLight directionalLight = new DirectionalLight();
		directionalLight.setColor(new Color3f(Color.white));
		directionalLight.setInfluencingBounds(bounds);
		branchGroup.addChild(directionalLight);
		// add sphere 1
		Transform3D sphereTransform3D = new Transform3D();
		/*
		 * Vector3d的x、y 和 z 值来替换本次变换的平移值 sphereTransform3D.setScale(0.4);
		 * 设置该变换的比例。使用该函数来调整对象的大小。
		 */
		sphereTransform3D.setTranslation(new Vector3d(0.1, 0.1, 0d));
		/*
		 * 请注意调用 rotX() 会删除矩阵中的非旋转组件。方法 rotY() 和 rotZ() 也是非常有用的。
		 * 角度以弧度指定，因此如果有必要，请使用 Math.toRadians(degrees)将角度从度转换成弧度。
		 */
		// sphereTransform3D.rotX(0.3d);// 将旋转组件设置成绕 X 轴逆时针旋转
		TransformGroup sphereGroup = new TransformGroup(sphereTransform3D);
		sphereGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
		sphereGroup.setTransform(sphereTransform3D);
		Sphere sphere = new Sphere(0.150f, -13, 100);
		// add appearance
		BufferedImage image = ImageIO.read(new File("D:/new_code_workspace/MyTest/src/res/ball-hdpi/ball2.png"));
		/*
		 * 为了看起来更真实，请总是将材质图像的宽度和高度设置成 2 的幂。其它的值会导致 TextureLoader 将材质压变形。
		 * 如果图像文件只有 RGB 值，而没有 alpha 值，则使用： TextureLoader texLoader = new
		 * TextureLoader(url,new String("RGB"),imageobserver)
		 */
		TextureLoader texloader = new TextureLoader(image, new String("RGB"));
		Appearance app = new Appearance();
		app.setTexture(texloader.getTexture());
		Material material = new Material();
		material.setDiffuseColor(new Color3f(0, 0, 0));
		material.setLightingEnable(true);
		material.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
		/*
		Alpha rotationAlpha = new Alpha(-1,Alpha.INCREASING_ENABLE,0,0,10, 2000);
		Color3f endColor = new Color3f(1.0f,1.0f,1.0f);
		Color3f startColor = new Color3f(0.0f,0.0f,0.0f);
		RotationInterpolator rotationInterp = new RotationInterpolator(rotationAlpha, sphereGroup,sphereTransform3D, 0.0f,(float)Math.PI*2.0f);
		
		rotationInterp.setSchedulingBounds(bounds);
		transformGroup.addChild(rotationInterp);
		*/
		app.setMaterial(material);
		app.setCapability(Appearance.ALLOW_TRANSPARENCY_ATTRIBUTES_WRITE);
		TextureAttributes textAttr = new TextureAttributes();
		textAttr.setTextureMode(TextureAttributes.REPLACE);
		app.setTextureAttributes(textAttr);
		sphere.setAppearance(app);
		sphereGroup.addChild(sphere);
		// add sphere 2
		/*TransformGroup sphereGroup2 = new TransformGroup();
		sphereGroup2.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
		Transform3D sphereTransform3D2 = new Transform3D();
		sphereTransform3D2.setTranslation(new Vector3d(0.3, 0, 0));
		sphereGroup2.setTransform(sphereTransform3D2);
		Sphere sphere2 = new Sphere(0.150f, -13, 100);
		// add appearance
		BufferedImage image2 = ImageIO.read(new File("D:/new_code_workspace/MyTest/src/res/ball-hdpi/ball12.png"));
		TextureLoader texloader2 = new TextureLoader(image2);
		Appearance app2 = new Appearance();
		app2.setTexture(texloader2.getTexture());
		Material material2 = new Material();
		material2.setDiffuseColor(new Color3f(1, 1, 1));
		material2.setLightingEnable(true);
		app2.setMaterial(material2);
		app2.setCapability(Appearance.ALLOW_TRANSPARENCY_ATTRIBUTES_WRITE);
		TextureAttributes textAttr2 = new TextureAttributes();
		textAttr2.setTextureMode(TextureAttributes.REPLACE);
		app2.setTextureAttributes(textAttr2);
		sphere2.setAppearance(app2);
		sphereGroup2.addChild(sphere2);*/

		transformGroup.addChild(sphereGroup);
		//transformGroup.addChild(sphereGroup2);
		branchGroup.addChild(transformGroup);
		branchGroup.compile();
		return branchGroup;
	}

	public static void main(String[] argsSes) throws IOException {
		new Ball().setVisible(true);
	}
}
